package org.brisling.common.util;

import java.io.IOException;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
/**
 * 
 * Json工具类，用户前后端数据传递时的实体对象与json标准数据对象的转换
 * @author : jackson wang
 * @Date   : 2015年6月8日 下午9:25:28
 * @version: 1.0
 */
public class JsonUtil {
	
	/**
	 * 单例模式，静态mapper对象，确保只有一个实例
	 */
	private static ObjectMapper mapper = null;
	
	/**
	 * 私有构造函数
	 */
	private  JsonUtil(){};
	
	
	/**
	 * 
	 * 将json字符串反序列化为指定类
	 * @param body	json数据
	 * @param clazz	反序列化类实体
	 * @param <T>   反序列化类
	 * @return T 经反序列化的<code>Class</code>实体
	 */
	public static <T extends Object>T  bodyToObj (String body,Class<T> clazz){
		ObjectMapper mapper = getMapper();
		
		try {
			T t =  mapper.readValue(body, clazz);
			return t;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	/**
	 * 
	 * 将json字符串反序列化为指定类
	 * @param body	json数据
	 * @param clazz	反序列化类实体
	 * @param <T>   反序列化类
	 * @return T 经反序列化的<code>Class</code>实体
	 */
	public static <E>E  body2Class (String body,Class<E> clazz){
		ObjectMapper mapper = getMapper();
		
		try {
			E t =  mapper.readValue(body, clazz);
			return t;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	/**
	 * 
	 * 将json字符串反序列化为指定类
	 * @param body	json数据
	 * @param clazz	反序列化类实体
	 * @param <T>   反序列化类
	 * @return T 经反序列化的<code>Class</code>实体
	 */
	@SuppressWarnings({ "rawtypes", "unchecked" })
	public static Object  bodyToClass (String body,Class clazz){
		ObjectMapper mapper = getMapper();
		
		try {
			Object t =  mapper.readValue(body, clazz);
			return t;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	
	
	/**
	 * 将json文本反序列化为指定类型的集合
	 * @param body		json文本
	 * @param clazz		集合内嵌对象类
	 * @param <T>   反序列化类
	 * @return List 经反序列化的<code>Class</code>集合
	 */
	public static List<Object> bodyToList (String body,Class<?> clazz){
		
		ObjectMapper mapper = getMapper();
		JavaType _javaType = mapper.getTypeFactory().constructCollectionType(List.class, clazz);
		
		List<Object> list = null;
		try {
			list =  mapper.readValue(body, _javaType);
			return list;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	/**
	 * 将json文本反序列化为指定类型的集合
	 * @param body		json文本
	 * @param clazz		集合内嵌对象类
	 * @param <T>   反序列化类
	 * @return List 经反序列化的<code>Class</code>集合
	 */
	public static <T> List<T> bodyToListClass (String body,Class<T> clazz){
		
		ObjectMapper mapper = getMapper();
		JavaType _javaType = mapper.getTypeFactory().constructCollectionType(List.class, clazz);
		
		List<T> list = null;
		try {
			list =  mapper.readValue(body, _javaType);
			return list;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	/**
	 * 将json文本反序列化为指定类型的集合
	 * @param body		json文本
	 * @param clazz		集合内嵌对象类
	 * @param <T>   反序列化类
	 * @return List 经反序列化的<code>Class</code>集合
	 */
	public static Map<String,Map<String,String>> bodyToMap (String body,Class<?> clazz){
		
		ObjectMapper mapper = getMapper();
		JavaType _javaType = mapper.getTypeFactory().constructMapType(Map.class, String.class,String.class);
		
		Map<String,Map<String,String>> list = null;
		try {
			list =  mapper.readValue(body, _javaType);
			return list;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	
	
	/**
	 * 将json文本反序列化为指定类型的集合
	 * @param body		json文本
	 * @param nodeName  json文本节点名称
	 * @param clazz		集合内嵌对象类
	 * @param <T>   反序列化类
	 * @return List     经反序列化的<code>Class</code>集合
	 */
	
	public static List<Object> bodyNodeToList (String body,String nodeName,Class<Object> clazz){
		
		ObjectMapper mapper = getMapper();
		
		if(body!=null&&nodeName!=null){
			JsonNode _node = null;
			try {
				_node  =  mapper.readTree(body);				
			} catch (IOException e1) {
				// TODO Auto-generated catch block
				e1.printStackTrace();
			}
			JsonNode groupNode = _node.get(nodeName);
			if(_node!=null)
				return bodyToList(groupNode.toString(),clazz);
		}
		return null;
	}
	
	/**
	 * 将json文本反序列化为指定类
	 * @param body		json文本
	 * @param clazz		集合内嵌对象类
	 * @param nodeName  json文本的节点名称
	 * @param <T>   反序列化类
	 * @return Object   经反序列化的<code>Class</code>实体
	 */
	
	public static  <T extends Object> T bodyNodeToClass (String body,String nodeName,Class<T> clazz){
		
		ObjectMapper mapper = getMapper();
		
		if(body!=null&&nodeName!=null){
			JsonNode _node = null;
			try {
				_node  =  mapper.readTree(body);				
			} catch (IOException e1) {
				// TODO Auto-generated catch block
				e1.printStackTrace();
			}
			JsonNode groupNode = _node.get(nodeName);
			if(_node!=null)
				return bodyToObj(groupNode.toString(),clazz);
		}
		return null;
	}
	
	@SuppressWarnings("rawtypes")
	public static String mapToJson(Map map){
//		ObjectMapper mapper = new ObjectMapper();
		ObjectMapper mapper = getMapper();
		
		String retStr = null;
		try {
			retStr =mapper.writeValueAsString(map);
		} catch (JsonProcessingException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return retStr;
	}	
	
	
	/**
	 * 實體對象輸出json
	 * @param obj
	 * @return
	 */
	public static String objToJson(Object obj){
//		ObjectMapper mapper = new ObjectMapper();
		ObjectMapper mapper = getMapper();
		
		String retStr = null;
		try {
			retStr =mapper.writeValueAsString(obj);
		} catch (JsonProcessingException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return retStr;
	}	
	
	
	/**
	 * 单例模式私有方法，确保Json Mapper 对象只有一个实例，所有针对mapper的配置在转换过程中有效
	 * @return ObjectMapper 单例mapper对象
	 */
	public static ObjectMapper getMapper(){
		if(mapper==null){
			mapper = new ObjectMapper();
			mapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);			
		}		
		return mapper;
	}
	
	/**
	 * 将json文本反序列化为指定类型的集合
	 * @param body		json文本
	 * @param clazz		集合内嵌对象类
	 * @param <T>   反序列化类
	 * @return List 经反序列化的<code>Class</code>集合
	 */
	public static List<Map<String,String>> bodyToListMap (String json){
		
		ObjectMapper mapper = getMapper();
		
		List<Map<String,String>> list = null;
		try {
			list =  mapper.readValue(json, new TypeReference<List<Map<String,String>>>(){});
			return list;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	
	/**
	 * 将json文本反序列化为指定类型的集合
	 * @param body		json文本
	 * @param clazz		集合内嵌对象类
	 * @param <T>   反序列化类
	 * @return List 经反序列化的<code>Class</code>集合
	 */
	public static List<LinkedHashMap<String,String>> bodyToListLinkedHashMap (String json){
		
		ObjectMapper mapper = getMapper();
		
		List<LinkedHashMap<String,String>> list = null;
		try {
			list =  mapper.readValue(json, new TypeReference<List<LinkedHashMap<String,String>>>(){});
			return list;
		} catch (IOException e1) {
			// TODO Auto-generated catch block
			e1.printStackTrace();
		}
		return null;
	}
	
	

}
